home *** CD-ROM | disk | FTP | other *** search
/ Sound Fx / Sound Fx.iso / Software / UNZIPED / SBPLY254 / SOURCE.ZIP / MOUSE.C < prev    next >
C/C++ Source or Header  |  1996-04-13  |  9KB  |  343 lines

  1. /* MOUSE - Module of mouse functions. To use it, include the MOUSE.H file
  2.  * in your program. The following functions are public:
  3.  *
  4.  *   MouseInit      - Initialize mouse
  5.  *   GetMouseEvent  - Get information about most recent mouse event
  6.  *   SetPtrVis      - Set visibility of pointer to HIDE or SHOW
  7.  *   SetPtrPos      - Set position of pointer
  8.  *   SetPtrShape    - Set shape of pointer in graphics modes, or
  9.  *                    character and color in text modes
  10.  *   GetPtrPos      - Get pointer position and button status
  11.  *
  12.  * The following structure is defined:
  13.  *
  14.  *   EVENT      -   Defines x, y, and mouse status of a mouse event
  15.  */
  16.  
  17. #include <graph.h>
  18. #include "mouse.h"
  19.  
  20. /* Internal information used by various mouse functions. */
  21. struct MOUINFO
  22. {
  23.     int      fExist, fInit, fGraph;
  24.     short    xVirtual,  yVirtual;
  25.     short    xActual,   yActual;
  26.     short    xLast,     yLast;
  27.     unsigned fsBtnLast, cBtn;
  28. } static mi =
  29. {
  30.     1, 0, 0,
  31.     0, 0,
  32.     0, 0,
  33.     0, 0,
  34.     0, 0
  35. };
  36.  
  37. /* MouseInit - Initialize mouse and turns on mouse pointer. Initializes
  38.  * all internal variables used by other mouse functions. This function
  39.  * should be called whenever a new video mode is set, since internal
  40.  * variables are mode-dependent.
  41.  *
  42.  * Params: none
  43.  *
  44.  * Return: 0 if no mouse available, otherwise number of buttons available
  45.  */
  46. int MouseInit()
  47. {
  48.     struct videoconfig vc;
  49.     char _far *pMode = (char _far *)0x00000449; /* Address for mode */
  50.  
  51.     /* Get video configuration. */
  52.     _getvideoconfig( &vc );
  53.  
  54.     /* Handle special case of Hercules graphics. To use mouse with video
  55.      * page 0. assume mode 6. To use mouse with page 1, assume mode 5.
  56.      * Since the mouse functions couldn't easily detect and adjust for
  57.      * page changes anyway, this code assumes page 0. Note also that the
  58.      * mouse for Hercules graphics must be set in text mono mode.
  59.      */
  60.     if( vc.mode == _HERCMONO )
  61.     {
  62.     _setvideomode( _TEXTMONO );
  63.     *pMode = 6;
  64.     }
  65.  
  66.     mi.fInit = 1;
  67.     _asm
  68.     {
  69.     sub     ax, ax              ; Mouse function 0, reset mouse
  70.     int     33h
  71.     mov     mi.fExist, ax       ; Set existence flag for future calls
  72.     or      ax, ax              ; If AX = 0, there is no mouse
  73.     jnz     exist
  74.     jmp     exit                ;   so quit
  75. exist:
  76.     mov     mi.cBtn, bx         ; Save number of mouse buttons for return
  77.     }
  78.  
  79.     /* Set graphics flag. */
  80.     if( vc.numxpixels )
  81.     {
  82.     mi.fGraph = 1;
  83.     mi.yActual = vc.numypixels - 1;
  84.     mi.xActual = vc.numxpixels - 1;
  85.     }
  86.     else
  87.     mi.fGraph = 0;
  88.  
  89.     /* The mouse works on a virtual screen of 640 x pixels by (8 * textrows)
  90.      * vertical pixels. By default, it assumes 640 x 200 for 25-line mode.
  91.      * You must call function 8 to adjust for other screen sizes.
  92.      */
  93.     mi.xVirtual = 639;
  94.     if( mi.fGraph )
  95.     mi.yVirtual = vc.numypixels - 1;
  96.     else
  97.     mi.yVirtual = (vc.numtextrows << 3) - 1;
  98.  
  99.     /* Reset Hercules graphics mode and reset the height. */
  100.     if( vc.mode == _HERCMONO )
  101.     {
  102.     _setvideomode( _HERCMONO );
  103.     mi.xVirtual = 719;
  104.     }
  105.  
  106.     _asm
  107.     {
  108.     mov     ax, 8               ; Set minimum and maximum vertical
  109.     sub     cx, cx              ; Minimum is 0
  110.     mov     dx, mi.yVirtual     ; Maximum is 8 * rows (or rows SHL 3)
  111.     int     33h                 ; Adjust for 25, 30, 43, 50, or 60 lines
  112.  
  113.     mov     ax, 1               ; Turn on mouse pointer
  114.     int     33h
  115.  
  116.     mov     ax, 3               ; Get initial position and button status
  117.     int     33h
  118.     mov     mi.xLast, cx        ; Save internally
  119.     mov     mi.yLast, dx
  120.     mov     mi.fsBtnLast, bx
  121.     }
  122. exit:    
  123.     return mi.cBtn;                 /* Return the number of mouse buttons */
  124. }
  125.  
  126. /* GetMouseEvent - Check to see if there has been a mouse event. If event
  127.  * occurred, update event structure.
  128.  *
  129.  * Params: pEvent - Pointer to event structure
  130.  *
  131.  * Return: 1 if event, 0 if no event
  132.  */
  133. int GetMouseEvent( EVENT _far *pEvent )
  134. {
  135.     int rtn;
  136.  
  137.     /* Make sure that mouse is initialized and exists. */
  138.     if( !mi.fInit )
  139.     MouseInit();
  140.     if( !mi.fExist )
  141.     return 0;
  142.  
  143.     _asm
  144.     {
  145.     mov     ax, 3               ; Get Mouse position and button status
  146.     int     33h
  147.     sub     ax, ax              ; Assume no event
  148.  
  149.     cmp     cx, mi.xLast        ; Has column changed?
  150.     jne     event
  151.     cmp     dx, mi.yLast        ; Has row changed?
  152.     jne     event
  153.     cmp     bx, mi.fsBtnLast    ; Has button changed?
  154.     je      noevent
  155. event:
  156.     mov     ax, 1               ; If something changed, event occurred
  157.     mov     mi.xLast, cx        ; Update internal variables
  158.     mov     mi.yLast, dx
  159.     mov     mi.fsBtnLast, bx
  160. noevent:
  161.     mov     rtn, ax             ; Set return value
  162.     }
  163.  
  164.     /* If event, put adjust values in structure. */
  165.     if( rtn )
  166.     {
  167.     /* If graphics mode, adjust virtual mouse position to actual
  168.      * screen coordinates.
  169.      */
  170.     if( mi.fGraph )
  171.     {
  172.         pEvent->x = ((long)mi.xLast * mi.xActual) / mi.xVirtual;
  173.         pEvent->y = ((long)mi.yLast * mi.yActual) / mi.yVirtual;
  174.     }
  175.     /* If text mode, adjust virtual mouse position to 1-based
  176.      * row/column.
  177.      */
  178.     else
  179.     {
  180.         pEvent->x = (mi.xLast >> 3) + 1;
  181.         pEvent->y = (mi.yLast >> 3) + 1;
  182.     }
  183.     pEvent->fsBtn = mi.fsBtnLast;
  184.     }
  185.     return rtn;
  186. }
  187.  
  188. /* GetPtrPos - Get mouse pointer position and button status regardless of
  189.  * whether there was an event.
  190.  *
  191.  * Params: pEvent - Pointer to event structure
  192.  *
  193.  * Return: 0 if no mouse, otherwise 1
  194.  */
  195. int GetPtrPos( EVENT _far *pEvent )
  196. {
  197.     /* Make sure that mouse is initialized and exists. */
  198.     if( !mi.fInit )
  199.     MouseInit();
  200.     if( !mi.fExist )
  201.     return 0;
  202.  
  203.     _asm
  204.     {
  205.     mov     ax, 3               ; Get Mouse position and button status
  206.     int     33h
  207.     les     di, pEvent
  208.     mov     es:[di].x, cx
  209.     mov     es:[di].y, dx
  210.     mov     es:[di].fsBtn, bx
  211.     }
  212.  
  213.     /* If graphics mode, adjust virtual mouse position to actual
  214.      * screen coordinates.
  215.      */
  216.     if( mi.fGraph )
  217.     {
  218.     pEvent->x = ((long)pEvent->x * mi.xActual) / mi.xVirtual;
  219.     pEvent->y = ((long)pEvent->y * mi.yActual) / mi.yVirtual;
  220.     }
  221.     /* If text mode, adjust virtual mouse position to 1-based
  222.      * row/column.
  223.      */
  224.     else
  225.     {
  226.     pEvent->x >>= 3;
  227.     pEvent->y >>= 3;
  228.     pEvent->x++;
  229.     pEvent->y++;
  230.     }
  231.     return 1;
  232. }
  233.  
  234. /* SetPtrVis - Set pointer visibility.
  235.  *
  236.  * Params: state - SHOW or HIDE
  237.  *
  238.  * Return: 0 if no mouse, otherwise 1
  239.  */
  240. int SetPtrVis( enum PTRVIS pv )
  241. {
  242.     /* Make sure that mouse is initialized and exists. */
  243.     if( !mi.fInit )
  244.     MouseInit();
  245.     if( !mi.fExist )
  246.     return 0;
  247.  
  248.     _asm
  249.     {
  250.     mov ax, pv                  ; Show or hide mouse pointer
  251.     int 33h
  252.     }
  253. }
  254.  
  255. /* SetPtrPos - Set mouse pointer position.
  256.  *
  257.  * Params: x - column position in text modes, actual x coordinate in graphics
  258.  *         y - row position in text modes, actual y coordinate in graphics
  259.  *
  260.  * Return: 0 if no mouse, otherwise 1
  261.  */
  262. int SetPtrPos( short x, short y )
  263. {
  264.     /* Make sure that mouse is initialized and exists. */
  265.     if( !mi.fInit )
  266.     MouseInit();
  267.     if( !mi.fExist )
  268.     return 0;
  269.  
  270.     /* If graphics, adjust actual coordinates to virtual coordinates. */
  271.     if( mi.fGraph )
  272.     {
  273.     x = ((long)x * mi.xActual) / mi.xVirtual;
  274.     y = ((long)y * mi.yActual) / mi.yVirtual;
  275.     }
  276.     /* If text, adjust row/column to 0-based virtual coordinates. */
  277.     else
  278.     {
  279.     x--;
  280.     y--;
  281.     x <<= 3;
  282.     y <<= 3;
  283.     }
  284.  
  285.     _asm
  286.     {
  287.     mov     ax, 4               ; Set mouse position
  288.     mov     cx, x
  289.     mov     dx, y
  290.     int     33h
  291.     }
  292.     return 1;
  293. }
  294.  
  295. /* SetPtrShape - Set mouse pointer shape.
  296.  *
  297.  * Params: x - column position in text modes, actual x coordinate in graphics
  298.  *         y - row position in text modes, actual y coordinate in graphics
  299.  *
  300.  * Return: 0 if no mouse, otherwise 1
  301.  */
  302. int SetPtrShape( PTRSHAPE _far *ps )
  303. {
  304.     /* Make sure that mouse is initialized and exists. */
  305.     if( !mi.fInit )
  306.     MouseInit();
  307.     if( !mi.fExist )
  308.     return 0;
  309.  
  310.     /* If graphics, use pointer shape bitmask array. */
  311.     if( mi.fGraph )
  312.     {
  313.     _asm
  314.     {
  315.         les     di, ps
  316.         mov     bx, es:[di].g.xHot      ; Load hot spot offsets
  317.         mov     cx, es:[di].g.yHot
  318.         mov     dx, di
  319.         add     dx, 4
  320.  
  321.         mov     ax, 9                   ; Set graphics pointer
  322.         int     33h
  323.     }
  324.     }
  325.     /* If text, use pointer color/character values. */
  326.     else
  327.     {
  328.     _asm
  329.     {
  330.         les     di, ps
  331.         mov     bx, 0                   ; Use software cursor
  332.         mov     cl, es:[di].t.chScreen
  333.         mov     ch, es:[di].t.atScreen
  334.         mov     dl, es:[di].t.chCursor
  335.         mov     dh, es:[di].t.atCursor
  336.  
  337.         mov     ax, 10                  ; Set text pointer
  338.         int     33h
  339.     }
  340.     }
  341.     return 1;
  342. }
  343.